home *** CD-ROM | disk | FTP | other *** search
/ Magnum One / Magnum One (Mid-American Digital) (Disc Manufacturing).iso / d12 / asm_msc1.arc / BRUN.ASM < prev    next >
Assembly Source File  |  1988-11-20  |  7KB  |  284 lines

  1. cseg    segment para public 'code'
  2. ; Copyright 1983 Data Base Decisions
  3.  
  4. ; This program is used to load an EXE file faster than BASIC.
  5. ; To use it, enter 'BRUN', after having poked the program name
  6. ; into the DOS communications area 0:4f0 - 0:4ff.
  7. ; This program is similar to, but different from RUN.COM. First,
  8. ; it is an EXE file, and can be run directly from a compiled BASIC
  9. ; program. Since compiled basic does not support the use of command
  10. ; line parameters, the name of the program to be run is put in the
  11. ; dos communications area. Be sure to follow the program name with
  12. ; at least one space. This program runs EXE programs only.
  13.  
  14. recct    equ 504         ; max recs per read
  15.  
  16. sseg    segment para stack 'stack'
  17.     db 16 dup('stack   ')
  18. sseg    ends
  19.  
  20. brun    proc far
  21.     assume cs:cseg,ds:cseg,ss:sseg,es:nothing
  22.  
  23.     cli            ; switch to internal stack
  24.     push cs
  25.     pop ss
  26.     mov sp,offset estak
  27.     sti
  28.     call p100        ; initialize
  29.     call p200        ; open file
  30.     jmp p300        ; copy this prog to hi memory
  31. p010:    call p400        ; read exe file to lo memory
  32.     jmp p600        ; relocate and execute prog
  33.  
  34. p050:    mov ah,9        ; print error message
  35.     int 21h
  36.     mov ax,oseg
  37.     push ax
  38.     xor ax,ax
  39.     push ax
  40.     ret 0            ; terminate
  41.  
  42. p100    proc near        ; initialize
  43.     mov ax,ds
  44.     mov si,2
  45.     mov bx,[si]        ; get top of memory from psp
  46.     push cs
  47.     pop ds            ; make ds=cs
  48.     push cs
  49.     pop es            ; make es=cs
  50.     mov oseg,ax        ; save original seg
  51.     add ax,10h
  52.     mov nseg,ax        ; save new prog seg
  53.     mov topmem,bx        ; save top of memory
  54.  
  55.     mov ax,offset endprog
  56.     add ax,15
  57.     and ax,0fff0h
  58.     mov eprog,ax        ; point to end of prog
  59.     mov cl,4
  60.     shr ax,cl
  61.     mov bx,ds
  62.     add ax,bx
  63.     mov dtads,ax        ; point to start dta
  64.  
  65.     push ds
  66.     mov ax,0
  67.     mov ds,ax
  68.     mov si,4f0h        ; point to dos comm area
  69.     mov di,offset fcb    ; work fcb
  70.     mov ax,2901h        ; parse file name
  71.     int 21h
  72.     pop ds
  73.  
  74.     mov di,offset fcb+9    ; make sure extension is 'EXE'
  75.     mov si,offset exe
  76.     mov cx,3
  77.     repnz movsb        ; copy 'EXE' to extension
  78.     ret
  79. p100    endp
  80.  
  81. p200    proc near        ; open file
  82.     mov dx,offset fcb
  83.     mov ah,0fh
  84.     int 21h
  85.     and al,0ffh        ; error?
  86.     jz p210         ; no
  87.     mov dx,offset errmsg1
  88.     jmp p050
  89.  
  90. p210:    mov si,offset fcb+16    ; get file size
  91.     mov ax,[si]        ; lower part
  92.     mov cl,7
  93.     shr ax,cl        ; divide by 128
  94.     mov bx,ax        ; hold in bx
  95.     mov ax,[si+2]        ; upper part of file size
  96.     mov cl,9
  97.     sal ax,cl        ; divide by 128
  98.     add ax,bx        ; total file size divided by 128
  99.     mov norecs,ax        ; save as norecs
  100.  
  101.     mov ax,128
  102.     mov si,offset fcb+14    ; set recsize = 128
  103.     mov [si],ax
  104.     mov al,0        ; zero 5 bytes in fcb
  105.     mov di,offset fcb+32
  106.     mov cx,5
  107.     repnz stosb        ; clear fcb bytes 32 - 36
  108.  
  109.     mov ax,norecs
  110.     mov cl,3
  111.     sal ax,cl        ; # of pghs for prog
  112.     add ax,dtads        ; top of prog (pghs)
  113.     mov bx,topmem        ; top of memory
  114.     sub bx,ax        ; is there room?
  115.     jae p220        ; yes
  116.     mov dx,offset errmsg4
  117.     jmp p050
  118.  
  119. p220:    ret
  120. p200    endp
  121.  
  122. p300:                ; read exe header
  123.     mov cx,4
  124.     call p500        ; read 4 recs
  125.     mov si,eprog
  126.     mov ax,[si]        ; get EXE signature
  127.     cmp ax,5a4dh        ; valid exe file?
  128.     jz p310         ; yes
  129.     mov dx,offset errmsg2
  130.     jmp p050
  131.  
  132. p310:                ; check stack placement
  133.     mov ax,[si+10h]     ; get value for sp
  134.     mov cl,4
  135.     shr ax,cl        ; convert to pghs
  136.     add ax,nseg        ; add base seg
  137.     add ax,[si+0eh]     ; and sp offset
  138.     mov bx,topmem        ; get top of memory
  139.     cmp bx,ax        ; is there room for the stack?
  140.     jae p315        ; yes
  141.     mov dx,offset errmsg4
  142.     jmp p050
  143.  
  144. p315:    mov ax,[si+8]        ; get header size (pghs)
  145.     mov cl,3
  146.     shr ax,cl        ; divide by 8 to get 128-byte records
  147.     sub ax,4        ; already read
  148.     mov cx,ax
  149.     jcxz p320        ; no more header
  150.     call p500        ; read rest of header
  151.  
  152. p320:    mov ax,norecs        ; recs left
  153.     mov cl,3
  154.     sal ax,cl        ; convert to pghs
  155.     add ax,nseg        ; plus start point gives copy destination
  156.     mov bx,dtads        ; end of header
  157.     cmp ax,bx        ; is start point above header?
  158.     jae p325        ; yes
  159.     mov ax,bx        ; no - change copy destination
  160.  
  161. p325:    mov es,ax        ; copy prog here
  162.     sub bx,oseg        ; minus psp gives pghs to copy
  163.     mov cl,3
  164.     sal bx,cl        ; words to copy
  165.     mov cx,bx
  166.     xor di,di
  167.     xor si,si
  168.     rep movsw        ; copy it
  169.  
  170.     mov di,offset p330
  171.     push es
  172.     push di
  173.     ret 0            ; jump to new copy
  174.  
  175. p330:    push es
  176.     pop ds            ; set ds=es=new cs
  177.     mov ax,es
  178.     mov ss,ax        ; set ss=es
  179.     jmp p010
  180.  
  181. p400    proc near        ; read file
  182.     mov ax,nseg
  183.     mov dtads,ax
  184. p410:    mov cx,norecs        ; # of records left
  185.     sub cx,recct        ; 63K worth?
  186.     ja p420         ; yes
  187.     add cx,recct        ; no - read remainder
  188.     jmp p430
  189.  
  190. p420:    mov cx,recct        ; read 63K
  191. p430:    call p500        ; read file
  192.  
  193. p440:    mov cx,norecs        ; any more to read?
  194.     jcxz p450        ; no
  195.     jmp p410        ; read next block
  196.  
  197. p450:    ret
  198. p400    endp
  199.  
  200. p500    proc near        ; read file - cx contains recs to read
  201.     push ds
  202.     mov bx,dtads
  203.     mov ds,bx        ; new ds
  204.     mov dx,0
  205.     mov ah,1ah
  206.     int 21h         ; set dta
  207.     pop ds
  208.     mov dx,offset fcb
  209.     mov ah,27h
  210.     int 21h         ; random block read
  211.     and al,0ffh        ; error?
  212.     jz p510         ; no
  213.     mov dx,offset errmsg3
  214.     jmp p050
  215.  
  216. p510:    mov ax,cx        ; adjust dta for next read
  217.     sub norecs,ax
  218.     mov cl,3
  219.     sal ax,cl        ; 8 pghs/record
  220.     add dtads,ax
  221.     ret
  222. p500 endp
  223.  
  224. p600:    mov ax,nseg        ; relocate and execute it
  225.     mov si,eprog
  226.     mov bx,si
  227.     add bx,[si+18h]     ; first relocation item
  228.     mov cx,[si+6]        ; # of items
  229.     jcxz p620        ; none
  230. p610:    mov dx,[bx+2]        ; get code seg
  231.     add dx,ax        ; add start seg
  232.     mov es,dx        ; in es
  233.     mov di,[bx]        ; set instruction in es
  234.     add es:[di],ax        ; add start seg
  235.     add bx,4        ; do another
  236.     loop p610        ; done?
  237.  
  238. p620:                ; pass control to exe prog
  239.     mov ax,nseg        ; new prog seg
  240.     add ax,[si+0eh]     ; plus ss offset gives new ss
  241.     cli
  242.     mov ss,ax
  243.     mov sp,[si+10h]
  244.     sti
  245.  
  246.     mov ax,nseg        ; new prog seg
  247.     add ax,[si+16h]     ; plus cs offset gives new cs
  248.     mov bx,[si+14h]     ; new ip
  249.     push ax
  250.     push bx
  251.  
  252.     mov ax,oseg        ; set up ds & es
  253.     mov ds,ax
  254.     mov es,ax
  255.  
  256.     mov ah,1ah        ; reset dta
  257.     mov dx,80h
  258.     int 21h
  259.     xor ax,ax        ; clear drive status
  260.  
  261.     ret 0            ; far return to exe prog
  262.  
  263. errmsg1 db 'Program not found',7,10,13,'$'
  264. errmsg2 db 'Header not found ',7,10,13,'$'
  265. errmsg3 db 'Unable to load program',7,10,13,'$'
  266. errmsg4 db 'Not enough memory',7,10,13,'$'
  267.  
  268. oseg    dw 0            ; original data seg
  269. nseg    dw 0            ; start of new prog
  270. topmem    dw 0            ; top of memory
  271. norecs    dw 0            ; # of 128 byte recs in file
  272. dtads    dw 0            ; dta data seg
  273. exe    db 'EXE'
  274. fcb    db 37 dup(0)        ; work fcb
  275. eprog    dw 0            ; end of this prog
  276. stak    db 16 dup('stack   ')   ; temp stack
  277. estak    db 0
  278.  
  279. endprog equ this word
  280.  
  281. brun    endp
  282. cseg    ends
  283. end    brun
  284.